
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.util.Enumeration;
import java.util.Stack;
import java.util.Vector;

import javax.servlet.RequestDispatcher;
import javax.servlet.Servlet;
import javax.servlet.ServletConfig;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.JspFactory;
import javax.servlet.jsp.JspWriter;
import javax.servlet.jsp.PageContext;
import javax.servlet.jsp.tagext.BodyContent;

import weblogic.servlet.internal.ChunkOutputWrapper;
import weblogic.servlet.internal.ServletRequestImpl;
import weblogic.servlet.jsp.BodyContentImpl;
import weblogic.servlet.jsp.JspWriterImpl;
import weblogic.servlet.jsp.NestedBodyResponse;
import weblogic.utils.UnsyncHashtable;
import weblogic.utils.io.FilenameEncoder;

public final class PageContextImpl extends PageContext
{
  private HttpServletRequest rq;
  private HttpServletResponse rp;
  protected Servlet servlet;
  protected ServletConfig config;
  protected ServletContext context;
  protected JspFactory factory;
  protected boolean needsSession;
  protected String errorPageURL;
  protected boolean autoFlush;
  protected int bufferSize;
  protected transient UnsyncHashtable attributes;
  protected transient JspWriter out;
  Stack writers = new Stack();

  public void initialize(Servlet paramServlet, ServletRequest paramServletRequest, ServletResponse paramServletResponse, String paramString, boolean paramBoolean1, int paramInt, boolean paramBoolean2)
    throws IllegalStateException, IllegalArgumentException, IOException
  {
    this.servlet = paramServlet;
    this.config = paramServlet.getServletConfig();
    this.context = paramServlet.getServletConfig().getServletContext();
    this.rq = ((HttpServletRequest)paramServletRequest);
    this.rp = ((HttpServletResponse)paramServletResponse);
    this.errorPageURL = paramString;
    this.needsSession = paramBoolean1;
    this.bufferSize = paramInt;
    this.autoFlush = paramBoolean2;
    this.attributes = new UnsyncHashtable();
    paramServletResponse.setBufferSize(paramInt);

    setAttribute("javax.servlet.jsp.jspOut", this.out);
    setAttribute("javax.servlet.jsp.jspRequest", this.rq);
    setAttribute("javax.servlet.jsp.jspResponse", this.rp);
    setAttribute("javax.servlet.jsp.jspPage", this.servlet);
    setAttribute("javax.servlet.jsp.jspConfig", this.config);
    setAttribute("javax.servlet.jsp.jspPageContext", this);
    setAttribute("javax.servlet.jsp.jspApplication", this.context);
  }

  public PageContextImpl(JspFactory paramJspFactory, Servlet paramServlet, ServletRequest paramServletRequest, ServletResponse paramServletResponse, String paramString, boolean paramBoolean1, int paramInt, boolean paramBoolean2)
    throws IOException, IllegalStateException, IllegalArgumentException
  {
    this.out = new JspWriterImpl(paramServletResponse, paramInt, paramBoolean2);
    initialize(paramServlet, paramServletRequest, paramServletResponse, paramString, paramBoolean1, paramInt, paramBoolean2);
  }

  private RequestDispatcher getRD(String paramString) throws IOException, ServletException {
    if (paramString.length() == 0)
      throw new ServletException("requested URL string is null");
    if (paramString.charAt(0) != '/')
    {
      localObject = (String)this.rq.getAttribute("javax.servlet.include.request_uri");
      if (localObject == null)
        localObject = ServletRequestImpl.getUnescapedURI(this.rq);
      int i = ((String)localObject).lastIndexOf('/');
      if (i == -1)
        paramString = '/' + paramString;
      else if (i == ((String)localObject).length() - 1)
        paramString = (String)localObject + paramString;
      else {
        paramString = ((String)localObject).substring(0, i + 1) + paramString;
      }

      String str1 = ServletRequestImpl.getUnescapedContextPath(this.rq);
      if (!str1.equals("/")) {
        paramString = paramString.substring(str1.length());
      }

      i = paramString.indexOf('?');
      String str2 = null;
      if (i != -1) {
        str2 = paramString.substring(i);
        paramString = paramString.substring(0, i);
      }
      paramString = FilenameEncoder.resolveRelativeURIPath(paramString);
      if (str2 != null) {
        paramString = paramString + str2;
      }
    }

    Object localObject = this.servlet.getServletConfig().getServletContext().getRequestDispatcher(paramString);
    if (localObject == null)
      throw new ServletException("no request dispatcher available for '" + paramString + "'");
    return (RequestDispatcher)localObject;
  }

  public void forward(String paramString) throws IOException, ServletException {
    getRD(paramString).forward(this.rq, this.rp);
  }

  public void include(String paramString) throws IOException, ServletException {
    getRD(paramString).include(this.rq, this.rp);
  }

  public JspWriter _createOut(int paramInt, boolean paramBoolean) {
    return this.out;
  }

  public void setAttribute(String paramString, Object paramObject)
  {
    this.attributes.put(paramString, paramObject); } 
  public Object getAttribute(String paramString) { return this.attributes.get(paramString); } 
  public void removeAttribute(String paramString) { this.attributes.remove(paramString); } 
  public JspWriter getOut() { return this.out; } 
  public HttpSession getSession() { return this.rq.getSession(false); } 
  public Object getPage() { return this.servlet; } 
  public ServletRequest getRequest() { return this.rq; } 
  public ServletResponse getResponse() { return this.rp; } 
  public Exception getException() { return (Exception)this.rq.getAttribute("javax.servlet.jsp.jspException"); } 
  public ServletConfig getServletConfig() { return this.servlet.getServletConfig(); } 
  public ServletContext getServletContext() { return getServletConfig().getServletContext();
  }

  public void release()
  {
    this.rq = null; this.rp = null; this.context = null; this.errorPageURL = null;
    this.attributes.clear();
    this.out = null;
    this.writers = null;
  }

  public void setAttribute(String paramString, Object paramObject, int paramInt) {
    switch (paramInt) {
    case 1:
      setAttribute(paramString, paramObject);
      break;
    case 2:
      this.rq.setAttribute(paramString, paramObject);
      break;
    case 4:
      this.context.setAttribute(paramString, paramObject);
      break;
    case 3:
      HttpSession localHttpSession = this.rq.getSession(true);
      localHttpSession.setAttribute(paramString, paramObject);
      break;
    default:
      throw new IllegalArgumentException("illegal scope: " + paramInt);
    }
  }

  public Object getAttribute(String paramString, int paramInt) {
    if (paramString == null) {
      return null;
    }
    switch (paramInt) {
    case 1:
      return getAttribute(paramString);
    case 2:
      return this.rq.getAttribute(paramString);
    case 4:
      return this.context.getAttribute(paramString);
    case 3:
      HttpSession localHttpSession = this.rq.getSession(false);
      return localHttpSession != null ? localHttpSession.getAttribute(paramString) : null;
    }
    throw new IllegalArgumentException("illegal scope: " + paramInt);
  }

  public Object findAttribute(String paramString)
  {
    Object localObject = null;
    localObject = getAttribute(paramString, 1);
    if (localObject == null) {
      localObject = getAttribute(paramString, 2);
      if (localObject == null) {
        localObject = getAttribute(paramString, 3);
        if (localObject == null)
          localObject = getAttribute(paramString, 4);
      }
    }
    return localObject;
  }

  public void removeAttribute(String paramString, int paramInt) {
    switch (paramInt) {
    case 1:
      removeAttribute(paramString);
      break;
    case 2:
      this.rq.removeAttribute(paramString);
      break;
    case 4:
      this.context.removeAttribute(paramString);
      break;
    case 3:
      HttpSession localHttpSession = this.rq.getSession(false);
      if (localHttpSession == null) break;
      localHttpSession.removeAttribute(paramString); break;
    default:
      throw new IllegalArgumentException("illegal scope: " + paramInt);
    }
  }

  public int getAttributesScope(String paramString) {
    if (getAttribute(paramString, 1) != null)
      return 1;
    if (getAttribute(paramString, 2) != null)
      return 2;
    if (getAttribute(paramString, 3) != null)
      return 3;
    if (getAttribute(paramString, 4) != null)
      return 4;
    return 0;
  }

  public Enumeration getAttributeNamesInScope(int paramInt) {
    switch (paramInt) {
    case 1:
      return this.attributes.keys();
    case 2:
      return this.rq.getAttributeNames();
    case 3:
      HttpSession localHttpSession = this.rq.getSession(false);
      if (localHttpSession == null) {
        return new Vector().elements();
      }
      return localHttpSession.getAttributeNames();
    case 4:
      return this.context.getAttributeNames();
    }
    throw new IllegalArgumentException("illegal scope: " + paramInt);
  }

  public void handlePageException(Throwable paramThrowable) throws ServletException, IOException {
    Throwable localThrowable = paramThrowable;
    Object localObject;
    if ((localThrowable instanceof ServletException)) {
      localObject = (ServletException)localThrowable;
      int i = 0;
      while (((((ServletException)localObject).getRootCause() instanceof ServletException)) && (i < 10))
      {
        localThrowable = ((ServletException)localObject).getRootCause();
        if (localObject == localThrowable) break;
        localObject = (ServletException)localThrowable;
        i++;
      }
      if (((ServletException)localObject).getRootCause() != null) localThrowable = ((ServletException)localObject).getRootCause();
    }

    this.rq.setAttribute("javax.servlet.jsp.jspException", localThrowable);
    this.rq.setAttribute("javax.servlet.error.request_uri", this.rq.getRequestURI());

    if (this.errorPageURL != null) {
      if (this.rp.isCommitted()) include(this.errorPageURL); else
        forward(this.errorPageURL);
      return;
    }
    if ((paramThrowable instanceof JspException)) {
      localObject = ((JspException)paramThrowable).getRootCause();
      if (localObject != null) {
        paramThrowable = (Throwable)localObject;
      }
    }

    if ((paramThrowable instanceof Error)) throw ((Error)paramThrowable);
    if ((paramThrowable instanceof RuntimeException)) throw ((RuntimeException)paramThrowable);
    if ((paramThrowable instanceof ServletException)) throw ((ServletException)paramThrowable);
    if ((paramThrowable instanceof IOException)) throw ((IOException)paramThrowable);
    throw new ServletException(paramThrowable);
  }

  public void handlePageException(Exception paramException) throws ServletException, IOException {
    Exception localException = paramException;
    handlePageException(localException);
  }

  public BodyContent pushBody()
  {
    this.writers.push(this.out);
    try {
      this.rp = new NestedBodyResponse(this.rp, this.out, this);
      this.out = ((NestedBodyResponse)this.rp).getBodyContentImpl();
    } catch (UnsupportedEncodingException localUnsupportedEncodingException) {
      throw new RuntimeException("unsupported charset: " + localUnsupportedEncodingException);
    }
    this.rq.setAttribute("javax.servlet.jsp.PageContext.out", this.out);
    ChunkOutputWrapper localChunkOutputWrapper = ((BodyContentImpl)this.out).co;
    this.rq.setAttribute("weblogic.servlet.BodyTagOutput", localChunkOutputWrapper);
    return (BodyContent)this.out;
  }

  public JspWriter popBody()
  {
    this.out = ((JspWriter)this.writers.pop());
    if ((this.rp instanceof NestedBodyResponse))
    {
      this.out = ((NestedBodyResponse)this.rp).getParentOut();

      this.rp = ((HttpServletResponse)((NestedBodyResponse)this.rp).getResponse());
    }

    if ((this.out instanceof BodyContentImpl)) {
      ChunkOutputWrapper localChunkOutputWrapper = ((BodyContentImpl)this.out).co;
      this.rq.setAttribute("weblogic.servlet.BodyTagOutput", localChunkOutputWrapper);
      this.rq.setAttribute("javax.servlet.jsp.PageContext.out", this.out);
    } else {
      this.rq.removeAttribute("weblogic.servlet.BodyTagOutput");
      this.rq.removeAttribute("javax.servlet.jsp.PageContext.out");
    }
    return this.out;
  }
}